package android.slc.appbase.repository.local;


import android.slc.commonlibrary.util.compat.SlcPathUtils;

import com.blankj.utilcode.util.CacheDiskUtils;
import com.blankj.utilcode.util.CacheDoubleUtils;
import com.blankj.utilcode.util.CacheMemoryUtils;
import com.blankj.utilcode.util.GsonUtils;
import com.blankj.utilcode.util.StringUtils;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

import java.util.HashMap;
import java.util.Map;

public class DbCd implements DataPersistence<DbCd> {
    private static Gson dbCdGson;
    private final String spName;
    private final CacheDoubleUtils spUtils;
    private final Map<String, Object> configMap;

    static {
        Gson dbCdGson = GsonUtils.getGson("dbCd");
        if (dbCdGson == null) {
            dbCdGson = new GsonBuilder().setPrettyPrinting().create();
            GsonUtils.setGson("dbCd", dbCdGson);
        }
        DbCd.dbCdGson = dbCdGson;
    }

    public DbCd(String spName) {
        this.spName = spName;
        spUtils = CacheDoubleUtils.getInstance(CacheMemoryUtils.getInstance(), CacheDiskUtils.getInstance(SlcPathUtils.createAppDbFile(spName)));
        String configValue = spUtils.getString(spName);
        if (StringUtils.isEmpty(configValue)) {
            configMap = new HashMap<>();
            configValue = GsonUtils.toJson(configMap);
            spUtils.put(spName, configValue);
        } else {
            configMap = GsonUtils.fromJson(configValue, GsonUtils.getMapType(String.class, Object.class));
        }
    }

    public int getInt(String key, int defValue, boolean autoSaveDefValue) {
        return DataPersistence.toInt(getValue(key, defValue, autoSaveDefValue));
    }

    public long getLong(String key, long defValue, boolean autoSaveDefValue) {
        return DataPersistence.toLong(getValue(key, defValue, autoSaveDefValue));
    }

    @Override
    public float getFloat(String key, float defValue, boolean autoSaveDefValue) {
        return DataPersistence.toFloat(getValue(key, defValue, autoSaveDefValue));
    }

    @Override
    public boolean getBoolean(String key, boolean defValue, boolean autoSaveDefValue) {
        return DataPersistence.toBoolean(getValue(key, defValue, autoSaveDefValue));
    }

    @Override
    public String getString(String key, String defValue, boolean autoSaveDefValue) {
        Object resultValue = getValue(key, defValue, autoSaveDefValue);
        if (resultValue != null) {
            return resultValue.toString();
        }
        return defValue;
    }

    @Override
    public Object getValue(String key, Object defValue, boolean autoSaveDefValue) {
        if (!getConfig().containsKey(key)) {
            if (autoSaveDefValue) {
                putValue(key, defValue);
            }
        }
        try {
            return getConfig().get(key);
        } catch (Exception e) {
            return defValue;
        }
    }

    @Override
    public synchronized DbCd putValue(String key, Object value) {
        return putValue(key, value, true);
    }

    public synchronized DbCd putValue(String key, Object value, boolean submit) {
        DataPersistence.checkValueType(value);
        configMap.put(key, value);
        if (submit) {
            submit();
        }
        return this;
    }

    @Override
    public synchronized DbCd putIfAbsent(String key, Object value) {
        putIfAbsent(key, value, true);
        return this;
    }

    public synchronized DbCd putIfAbsent(String key, Object value, boolean submit) {
        DataPersistence.super.putIfAbsent(key, value);
        if (submit) {
            submit();
        }
        return this;
    }

    private synchronized Map<String, Object> getConfig() {
        return configMap;
    }

    public synchronized void submit() {
        spUtils.put(spName, GsonUtils.toJson(DbCd.dbCdGson, configMap));
    }

}
